package edu.richmond.is.webservices.files2exist;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map.Entry;
import java.util.Set;
import java.util.StringTokenizer;

/**
 * This class takes the public domain formatted
 * mime-types files, as distributed with the apache
 * httpd server, and provides and interface for
 * categorizing files as to their mime-type.
 *
 */
public class MimeTypeMapper {

	private HashMap<String, String> mimeMappings = new HashMap<String, String>();
	
	public MimeTypeMapper(String mimeTypesFileLoc) throws IOException {
		File mappingFile = new File(mimeTypesFileLoc);
		if(!mappingFile.exists()) {
			throw new FileNotFoundException("Mime-types file does not exist:" + mappingFile);
		}
		
		parseMappings(mappingFile);
	}

	private void parseMappings(File mappingFile) throws IOException {
		BufferedReader rdr = null;
		try {
			rdr = new BufferedReader(new FileReader(mappingFile));

			String line = rdr.readLine();
			while(line != null) {
				line = line.trim();
				//
				// Filter blank lines and comments
				//
				if(line.length() != 0 && !line.startsWith("#")) {
					
					StringTokenizer tok = new StringTokenizer(line);
					String mime = tok.nextToken();
					while(tok.hasMoreTokens()) {
						mimeMappings.put(tok.nextToken().toLowerCase(), mime);
					}
					
				}
				line = rdr.readLine();
			}
		} finally {
			if(rdr != null) {
				rdr.close();
			}

		}
	}
	
	/**
	 * For a given file, determine its mime-type.
	 * 
	 * @param file File to categorize
	 * @return Mime-type string
	 * @throws MimeMappingNotFoundException If no mapping is found for the files extention
	 */
	public String findMimeMapping(File file) throws MimeMappingNotFoundException {
		String fName = file.getName();
		int lastDot = fName.lastIndexOf(".");
		
		String lastToken = fName.substring(lastDot + 1);
		String mime = mimeMappings.get(lastToken.toLowerCase());
		if(mime == null) {
			throw new MimeMappingNotFoundException("Unable to resolve mime type for extension='" + lastToken + "'");
		}
		return mime;
	}
	

	/**
	 * For a given mime-type string, return
	 * whether or not it is an xml type
	 * 
	 * @param mimeType Mime-type string as returned by findMimeMapping
	 * @return true if xml mime-type, false otherwise
	 */
	public boolean isXMLMimeType(String mimeType) {
		//
		// Assume all xml mime types contain
		// the string "xml"
		//
		return mimeType.toLowerCase().contains("xml");
	}
	
	public static class MimeMappingNotFoundException extends Exception {

		public MimeMappingNotFoundException(String msg) {
			super(msg);
		}
		
	}
	
	public static void main(String args[]) throws Exception {
		MimeTypeMapper mapper = new MimeTypeMapper(args[0]);
		Set<Entry<String, String>> ents = mapper.mimeMappings.entrySet();
		for(Entry<String, String> ent: ents) {
			System.err.println(ent);
		}
		System.err.println(mapper.findMimeMapping(new File("myfile.xMl.txt.jar")));
	}


}
